package vn.fpt.fsoft.controller;

/*
 * Government Office Region controller.
 *
 * Version 1.0
 *
 * 22-August-2014
 *
 * Modification Logs:
 * DATE                 AUTHOR              DESCRIPTION
 * --------------------------------------------------------
 * 22-August-2014       NguyenTuyen          Create GovRegionDAO
 */
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import com.google.gson.JsonArray;
import com.google.gson.JsonObject;

import vn.fpt.fsoft.dao.CountryDAO;
import vn.fpt.fsoft.dao.CountyDAO;
import vn.fpt.fsoft.dao.GovOfficeRegionDAO;
import vn.fpt.fsoft.entity.Country;
import vn.fpt.fsoft.entity.County;
import vn.fpt.fsoft.entity.GovOfficeRegion;

/**
 * Servlet implementation class ListGovOfficeRegionController
 */
@WebServlet("/ListGovOfficeRegionController")
public class ListGovOfficeRegionController extends HttpServlet {
    /**
     * serialVersionUID.
     */
    private static final long serialVersionUID = 1L;
    
    /**
     * List country.
     */
    private List<Country> ctr = new CountryDAO().getAllCountry();
    
    /**
     * List county.
     */
    private List<County> listCounty = null;
    
    /**
     * A object of Government office region.
     */
    private GovOfficeRegion gov = new GovOfficeRegion();
    
    /**
     * County.
     */
    private County county = new County();
    
    /**
     * @see HttpServlet#HttpServlet()
     */
    public ListGovOfficeRegionController() {
        super();
        // TODO Auto-generated constructor stub
    }
    
    /**
     * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse
     *      response)
     */
    @SuppressWarnings("unchecked")
    protected void doGet(HttpServletRequest request,
            HttpServletResponse response) throws ServletException, IOException {
        // TODO Auto-generated method stub
        String action = request.getParameter("action");
        
        if (request.getSession().getAttribute("ListCounty") == null) {
            listCounty = getAllCounty();
            request.getSession().setAttribute("ListCounty", listCounty);
        } else {
            listCounty = (List<County>) request.getSession().getAttribute(
                    "ListCounty");
        }
        
        if ("getdata".equals(action)) {
            doGetData(request, response, listCounty);
        } else if ("add".equals(action)) {
            boolean res = doGetAdd(request, response);
            if (res) {
                List<GovOfficeRegion> list = new GovOfficeRegionDAO()
                        .getAllGovOfficeRegion();
                request.getSession().setAttribute("listGovOfficeRegion", list);
                request.getSession().setAttribute("currentListGovOfficeRegion",
                        list);
                response.getWriter().write("Create successful!!!");
            } else {
                response.getWriter().write("Fail!!!!");
            }
        } else if ("view".equals(action)) {
            doGetView(request, response);
        } else if ("saveupdate".equals(action)) {
            boolean res = doGetUpdate(request, response);
            if (res) {
                List<GovOfficeRegion> list = new GovOfficeRegionDAO()
                        .getAllGovOfficeRegion();
                request.getSession().setAttribute("listGovOfficeRegion", list);
                request.getSession().setAttribute("currentListGovOfficeRegion",
                        list);
                response.getWriter().write("Update successful!!!");
            } else {
                response.getWriter().write("Fail!!!!");
            }
        } else {
            doGetViewUpdate(request, response, listCounty);
        }
    }
    
    /**
     * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse
     *      response)
     */
    @SuppressWarnings("unchecked")
    protected void doPost(HttpServletRequest request,
            HttpServletResponse response) throws ServletException, IOException {
        // TODO Auto-generated method stub
        List<GovOfficeRegion> list = new ArrayList<GovOfficeRegion>();
        boolean checked = Boolean.parseBoolean(request.getParameter("checked"));
        String cond = request.getParameter("condition");
        String govOfficeRegionID = request.getParameter("govofficetregionid");
        boolean isActive = Boolean.parseBoolean(request
                .getParameter("isactive"));
        
        // List Government Office Region Basic
        if (request.getSession().getAttribute("listGovOfficeRegion") == null) {
            list = getAllGovOfficeRegion();
            request.getSession().setAttribute("listGovOfficeRegion", list);
            request.getSession().setAttribute("currentListGovOfficeRegion",
                    list);
        } else { // Tranh goi toi database nhieu lan
            list = (List<GovOfficeRegion>) request.getSession().getAttribute(
                    "listGovOfficeRegion");
            request.getSession().setAttribute("currentListGovOfficeRegion",
                    list);
        }
        
        // Update active
        if (govOfficeRegionID != null) {
            updateGovOfficeRegion(Integer.parseInt(govOfficeRegionID), isActive);
            list = getAllGovOfficeRegion();
            request.getSession().setAttribute("listGovOfficeRegion", list);
            request.getSession().setAttribute("currentListGovOfficeRegion",
                    list);
        }
        
        // List Government Office Region Filter
        if (cond != null) {
            list = filterGovOfficeRegion(cond, list);
            request.getSession().setAttribute("currentListGovOfficeRegion",
                    list);
            if (!checked) {
                list = getGovOfficeRegionIsActive(list);
            }
        } else {
            list = (List<GovOfficeRegion>) request.getSession().getAttribute(
                    "currentListGovOfficeRegion");
            if (!checked) {
                list = getGovOfficeRegionIsActive(list);
            }
        }
        
        // To convert use jsp
        if (list != null) {
            String json = convertListToJSon(list);
            response.getWriter().write(json);
        }
        
    }
    
    /**
     * Convert a list to json (a string).
     * 
     * @param list
     * @return
     */
    private String convertListToJSon(List<GovOfficeRegion> list) {
        JsonObject responeseDetailJson = new JsonObject();
        JsonObject jsonObject;
        JsonArray jsonArray = new JsonArray();
        
        for (GovOfficeRegion gov : list) {
            jsonObject = new JsonObject();
            jsonObject.addProperty("GovOfficeRegionID",
                    gov.getGovOfficeRegionID());
            jsonObject.addProperty("GovOfficeRegionName",
                    gov.getGovOfficeRegionName());
            jsonObject.addProperty("Description", gov.getDescription());
            jsonObject.addProperty("CountyName", gov.getCounty()
                    .getCountyName());
            jsonObject.addProperty("IsActive", gov.isActive());
            jsonArray.add(jsonObject);
        }
        responeseDetailJson.add("GovOfficeRegion", jsonArray);
        return String.valueOf(responeseDetailJson);
    }
    
    /**
     * Get all government office region.
     * 
     * @return
     */
    private List<GovOfficeRegion> getAllGovOfficeRegion() {
        return new GovOfficeRegionDAO().getAllGovOfficeRegion();
    }
    
    /**
     * Get government office region with is active = true.
     * 
     * @param list
     * @return
     */
    private List<GovOfficeRegion> getGovOfficeRegionIsActive(
            List<GovOfficeRegion> list) {
        List<GovOfficeRegion> listActive = new ArrayList<GovOfficeRegion>();
        for (GovOfficeRegion gov : list) {
            if (gov.isActive()) {
                listActive.add(gov);
            }
        }
        return listActive;
    }
    
    /**
     * Update active government office region.
     * 
     * @param govOfficeRegionID
     * @return
     */
    private boolean updateGovOfficeRegion(int govOfficeRegionID,
            boolean isActive) {
        GovOfficeRegion gov = new GovOfficeRegionDAO()
                .getGovOfficeRegionByID(govOfficeRegionID);
        if (isActive) {
            gov.setActive(false);
        } else {
            gov.setActive(true);
        }
        return new GovOfficeRegionDAO().updateGovOfficeRegion(gov);
    }
    
    /**
     * Get list county.
     * 
     * @return
     */
    private List<County> getAllCounty() {
        return new CountyDAO().getAllCounty();
    }
    
    /**
     * Get county where countyID.
     * 
     * @param countyID
     * @return
     */
    private County getCountyByID(int countyID) {
        return new CountyDAO().getCountyByID(countyID);
    }
    
    /**
     * Get Government Office Region with id.
     * 
     * @param govOfficeRegionID
     * @return
     */
    private GovOfficeRegion getGovOfficeRegionByID(int govOfficeRegionID) {
        return new GovOfficeRegionDAO()
                .getGovOfficeRegionByID(govOfficeRegionID);
    }
    
    /**
     * Get Government Office Region with name.
     * 
     * @param govOfficeRegionName
     * @return
     */
    private List<GovOfficeRegion> getGovOfficeRegionByName(
            String govOfficeRegionName) {
        return new GovOfficeRegionDAO()
                .getGovOfficeRegionByName(govOfficeRegionName);
    }
    
    /**
     * Add new government office region.
     * 
     * @param gov
     * @return
     */
    private boolean addGovOfficeRegion(GovOfficeRegion gov) {
        return new GovOfficeRegionDAO().addGovOfficeRegion(gov);
    }
    
    /**
     * Update government office region.
     * 
     * @param gov
     * @return
     */
    public boolean updateGovOfficeRegion(GovOfficeRegion gov) {
        return new GovOfficeRegionDAO().updateGovOfficeRegion(gov);
    }
    
    /**
     * Filter government office region by condition.
     * 
     * @param cond
     * @param list
     * @return
     */
    private List<GovOfficeRegion> filterGovOfficeRegion(String cond,
            List<GovOfficeRegion> list) {
        List<GovOfficeRegion> listFilterGov = new ArrayList<GovOfficeRegion>();
        char leter;
        if ("all".equals(cond)) {
            return list;
        } else if ("digital".equals(cond)) {
            for (GovOfficeRegion gov : list) {
                if (Character.isDigit(gov.getGovOfficeRegionName().charAt(0))) {
                    listFilterGov.add(gov);
                }
            }
        } else if ("ae".equals(cond)) {
            for (GovOfficeRegion gov : list) {
                leter = Character.toLowerCase(gov.getGovOfficeRegionName()
                        .charAt(0));
                if (leter >= 'a' && leter <= 'e') {
                    listFilterGov.add(gov);
                }
            }
        } else if ("fj".equals(cond)) {
            for (GovOfficeRegion gov : list) {
                leter = Character.toLowerCase(gov.getGovOfficeRegionName()
                        .charAt(0));
                if (leter >= 'f' && leter <= 'j') {
                    listFilterGov.add(gov);
                }
            }
        } else if ("kn".equals(cond)) {
            for (GovOfficeRegion gov : list) {
                leter = Character.toLowerCase(gov.getGovOfficeRegionName()
                        .charAt(0));
                if (leter >= 'k' && leter <= 'n') {
                    listFilterGov.add(gov);
                }
            }
        } else if ("or".equals(cond)) {
            for (GovOfficeRegion gov : list) {
                leter = Character.toLowerCase(gov.getGovOfficeRegionName()
                        .charAt(0));
                if (leter >= 'o' && leter <= 'r') {
                    listFilterGov.add(gov);
                }
            }
        } else if ("sv".equals(cond)) {
            for (GovOfficeRegion gov : list) {
                leter = Character.toLowerCase(gov.getGovOfficeRegionName()
                        .charAt(0));
                if (leter >= 's' && leter <= 'v') {
                    listFilterGov.add(gov);
                }
            }
        } else if ("wz".equals(cond)) {
            for (GovOfficeRegion gov : list) {
                leter = Character.toLowerCase(gov.getGovOfficeRegionName()
                        .charAt(0));
                if (leter >= 'w' && leter <= 'z') {
                    listFilterGov.add(gov);
                }
            }
        }
        return listFilterGov;
    }
    
    /**
     * doGetData.
     * 
     * @param request
     * @param response
     * @param listCounty
     * @throws IOException
     */
    private void doGetData(HttpServletRequest request,
            HttpServletResponse response, List<County> listCounty)
            throws IOException {
        String result = "";
        result += "<option value=0></option>";
        for (Country ct : ctr) {
            result += "<optgroup label=\"" + ct.getCountryName() + "\">";
            for (County c : listCounty) {
                if (c.getCountry().getCountryID() == ct.getCountryID()) {
                    result += "<option value=" + c.getCountyID() + ">"
                            + c.getCountyName() + "</option>";
                }
            }
            result += "</optgroup>";
        }
        response.getWriter().write(result);
    }
    
    /**
     * Thuc hien add tren doGet.
     * 
     * @param request
     * @param response
     * @param county
     * @param gov
     * @return
     */
    private boolean doGetAdd(HttpServletRequest request,
            HttpServletResponse response) {
        county = getCountyByID(Integer.parseInt(request
                .getParameter("countyid")));
        gov.setGovOfficeRegionName(request.getParameter("govname"));
        gov.setDescription(request.getParameter("description"));
        gov.setCounty(county);
        gov.setCountryID(county.getCountry().getCountryID());
        gov.setActive(true);
        return addGovOfficeRegion(gov);
    }
    
    /**
     * doGetView.
     * 
     * @param request
     * @param response
     * @return
     * @throws IOException
     */
    private void doGetView(HttpServletRequest request,
            HttpServletResponse response) throws IOException {
        gov = getGovOfficeRegionByID(Integer.parseInt(request
                .getParameter("govID")));
        List<GovOfficeRegion> listGov = getGovOfficeRegionByName(gov
                .getGovOfficeRegionName());
        String result = "";
        result += "<tr>";
        result += "<td>Government Office Region name</td>";
        result += "<td><input id=\"name\" type=\"text\" size=\"32\" disabled=\"disabled\" value=\""
                + gov.getGovOfficeRegionName() + "\"/></td>";
        result += "</tr>";
        result += "<tr>";
        result += "<td height=\"100\">Description</td>";
        result += "<td><textarea id=\"description\" rows=\"4\" cols=\"32\" disabled=\"disabled\">";
        for (GovOfficeRegion gov1 : listGov) {
            if(gov1.getDescription() == null){
                result += " -No description\n"; 
            }else{
                result += " - " + gov1.getDescription() + "\n";
            }
        }
        result += "</textarea></td>";
        result += "</tr>";
        result += "<tr>";
        result += "<td>County</td>";
        result += "<td><textarea id=\"county\" rows=\"4\" cols=\"32\" disabled=\"disabled\">";
        for (GovOfficeRegion gov1 : listGov) {
            result += " - " + gov1.getCounty().getCountyName() + "\n";
        }
        result += "</textarea></td>";
        result += "</tr>";
        response.getWriter().write(result);
    }
    
    /**
     * do get update.
     * 
     * @param request
     * @param response
     * @param county
     * @param g
     * @return
     */
    private boolean doGetUpdate(HttpServletRequest request,
            HttpServletResponse response) {
        county = getCountyByID(Integer.parseInt(request
                .getParameter("countyid")));
        GovOfficeRegion g = getGovOfficeRegionByID(Integer.parseInt(request
                .getParameter("idGov")));
        g.setGovOfficeRegionName(request.getParameter("govname"));
        g.setDescription(request.getParameter("description"));
        g.setCounty(county);
        g.setCountryID(county.getCountry().getCountryID());
        return updateGovOfficeRegion(g);
    }
    
    /**
     * doGetViewUpdate.
     * 
     * @param request
     * @param response
     * @param listCounty
     * @throws IOException
     */
    private void doGetViewUpdate(HttpServletRequest request,
            HttpServletResponse response, List<County> listCounty)
            throws IOException {
        gov = getGovOfficeRegionByID(Integer.parseInt(request
                .getParameter("govofficeregionid")));
        String result = "";
        result += "<tr>";
        result += "<td>Government Office Region name</td>";
        result += "<td><input id=\"name\" type=\"text\" size=\"32\" value=\""
                + gov.getGovOfficeRegionName() + "\"/></td>";
        result += "</tr>";
        result += "<tr>";
        result += "<td height=\"100\">Description</td>";
        if(gov.getDescription()==null){
            result += "<td><textarea id=\"description\" rows=\"4\" cols=\"32\">No description</textarea></td>";
        }else{
            result += "<td><textarea id=\"description\" rows=\"4\" cols=\"32\">"
                + gov.getDescription() + "</textarea></td>";
        }
        result += "</tr>";
        result += "<tr>";
        result += "<td>County</td>";
        result += "<td><select id=\"county\" style=\"width: 63%;\">";
        result += "<option value=" + gov.getCounty().getCountyID() + ">"
                + gov.getCounty().getCountyName() + "-"
                + gov.getCounty().getCountry().getCountryName() + "</option>";
        result += "<option value=0></option>";
        for (Country ct : ctr) {
            result += "<optgroup label=\"" + ct.getCountryName() + "\">";
            for (County c : listCounty) {
                if (c.getCountry().getCountryID() == ct.getCountryID()
                        && c.getCountyID() != gov.getCounty().getCountyID()) {
                    result += "<option value = " + c.getCountyID() + ">"
                            + c.getCountyName() + "</option>";
                }
            }
            result += "</optgroup>";
        }
        result += "</select>";
        result += "</td>";
        response.getWriter().write(result);
    }
}
